package com.quectel.cms.controller.forum;


import cn.hutool.core.date.DatePattern;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.lang.func.LambdaUtil;
import com.quectel.business.common.forum.ForumMuteBusiness;
import com.quectel.business.common.forum.vo.ForumMuteVo;
import com.quectel.business.common.mobileuser.MobileUserBusiness;
import com.quectel.business.common.mobileuser.MobileUserMsgBusiness;
import com.quectel.business.common.util.sys.SysCodeUtils;
import com.quectel.cms.controller.BaseController;
import com.quectel.cms.interceptor.LoginUserSession;
import com.quectel.cms.util.SessionHolder;
import com.quectel.constant.PushConstants;
import com.quectel.constant.core.forum.ForumConstants;
import com.quectel.constant.core.mobileuser.MobileUserMsgConstants;
import com.quectel.constant.global.SystemConstants;
import com.quectel.constant.global.annotation.RequirePermissions;
import com.quectel.constant.sys.SysCodeKeyConstants;
import com.quectel.core.module.forum.dto.ForumMuteDto;
import com.quectel.core.module.forum.dto.ForumMuteRecordDto;
import com.quectel.core.module.forum.dto.ForumMuteReq;
import com.quectel.core.module.forum.dto.mongo.ForumCommentDto;
import com.quectel.core.module.forum.dto.mongo.ForumPostDto;
import com.quectel.core.module.forum.service.ForumMuteRecordService;
import com.quectel.core.module.forum.service.ForumMuteService;
import com.quectel.core.module.forum.service.mongo.ForumCommentService;
import com.quectel.core.module.forum.service.mongo.ForumPostService;
import com.quectel.core.module.household.dto.HouseholdDto;
import com.quectel.core.module.household.service.HouseholdService;
import com.quectel.core.module.mobileuser.dto.MobileUserDto;
import com.quectel.core.module.mobileuser.service.MobileUserService;
import com.quectel.sys.module.sys.dto.SysUserDto;
import com.quectel.sys.module.sys.service.SysUserService;
import com.quectel.util.common.*;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.dubbo.config.annotation.DubboReference;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletResponse;
import java.util.*;

/**
 * @author bob
 * @email bob.yu@quectel.com
 * @date 2023/05/10 11:21
 */
@RestController
@RequestMapping("forumMute")
@Tag(name = "ForumMuteController", description = "邻友圈禁言管理相关api")
public class ForumMuteController extends BaseController {

    public static final String SOURCEIDS = "sourceIds";
    private static final String EXEC_TIME = "execTime";

    @DubboReference
    private ForumMuteService forumMuteService;
    @DubboReference
    private ForumPostService forumPostService;
    @DubboReference
    private ForumCommentService forumCommentService;
    @DubboReference
    private MobileUserService mobileUserService;
    @DubboReference
    private ForumMuteRecordService forumMuteRecordService;
    @DubboReference
    private SysUserService sysUserService;
    @DubboReference
    private HouseholdService householdService;

    @Autowired
    private MobileUserBusiness mobileUserBusiness;
    @Autowired
    private ForumMuteBusiness forumMuteBusiness;
    @Autowired
    private MobileUserMsgBusiness mobileUserMsgBusiness;

    @PostMapping("mute")
    @Operation(summary = "禁言")
    @RequirePermissions(values = "forumMute:mute")
    public Response<Object> mute(
            @RequestBody ForumMuteReq forumMuteReq) {

        ForumMuteVo muteStatus = forumMuteBusiness.getMuteStatus(SessionHolder.getSysUser().getTenantId(), forumMuteReq.getMobileUserId());
        //用户已经被禁言,无须操作
        if (SystemConstants.NO.equals(muteStatus.getStatus())) {
            return Response.error(muteStatus.getRecordText());
        }

        MobileUserDto mobileUserDto = mobileUserService.selectCacheById(forumMuteReq.getMobileUserId());
        if (mobileUserDto == null) {
            return Response.error("用户不存在");
        }

        forumMuteReq.setTenantId(SessionHolder.getSysUser().getTenantId());
        forumMuteReq.setAuditUserId(SessionHolder.getSysUserId());

        forumMuteService.mute(forumMuteReq);

        Long villageId = null;
        if (ForumConstants.ForumAuditObjectEnum.POST.getType().equals(forumMuteReq.getSourceType())) {
            ForumPostDto forumPostDto = forumPostService.selectCacheById(forumMuteReq.getSourceId());
            if (forumPostDto != null) {
                villageId = forumPostDto.getVillageId();
            }
        }

        if (ForumConstants.ForumAuditObjectEnum.COMMENT.getType().equals(forumMuteReq.getSourceType())) {
            ForumCommentDto forumCommentDto = forumCommentService.selectCacheById(forumMuteReq.getSourceId());
            if (forumCommentDto != null) {
                Long householdId = forumCommentDto.getHouseholdId();
                HouseholdDto householdDto = householdService.selectCacheById(householdId);
                if (householdDto != null) {
                    villageId = householdDto.getVillageId();
                }
            }
        }

        List<String> violationTypeStringList = new ArrayList<>(forumMuteReq.getViolationTypes().size());
        for (Byte violationType : forumMuteReq.getViolationTypes()) {
            String s = SysCodeUtils.easyToGetName(SysCodeKeyConstants.FORUM_VIOLATION_TYPE, String.valueOf(violationType));
            violationTypeStringList.add(s);
        }


        LoginUserSession sysUser = SessionHolder.getSysUser();
        if (villageId != null) {
            mobileUserMsgBusiness.pushMsg(
                    sysUser.getTenantId(),
                    villageId,
                    Collections.singletonList(mobileUserDto),
                    MobileUserMsgConstants.SourceType.FORUM_MSG,
                    forumMuteReq.getSourceId(),
                    MobileUserMsgConstants.SourceType.FORUM_MSG.getDefaultTitle(),
                    "您因违反" + JacksonUtils.toJsonString(violationTypeStringList) + "被管理员禁言，禁言时间为" + DateUtils.format(forumMuteReq.getStartTime(), DateUtils.FormatType.SIMPLE) + "~" + DateUtils.format(forumMuteReq.getEndTime(), DateUtils.FormatType.SIMPLE),
                    true,
                    new PushConstants.PushType[]{PushConstants.PushType.WECHAT_OFFICIAL}

            );
        }

        return Response.ok();
    }


    @GetMapping("muteStatus")
    @Operation(summary = "校验用户是否被禁言")
    @RequirePermissions(values = {"forumMute:info", "forumMute:mute"})
    public Response<Object> muteStatus(
            @Parameter(description = "用户Id") @RequestParam(required = false) Long userId
    ) {

        // 先判断禁言用户表是否存在，不存在就返回正常状态
        Map<String, Object> sqlMap = new HashMap<>();
        sqlMap.put(LambdaUtil.getFieldName(ForumMuteDto::getTenantId), SessionHolder.getSysUser().getTenantId());
        sqlMap.put(LambdaUtil.getFieldName(ForumMuteDto::getMobileUserId), userId);
        int queryTotal = forumMuteService.queryTotal(sqlMap);
        if (queryTotal == 0) {
            return Response.ok();
        } else {
            // 查询到不是空，去查询当前是否在记录区间内
            sqlMap.put(EXEC_TIME, DateUtils.format(new Date(), DateUtils.FormatType.SIMPLE));
            int total = forumMuteRecordService.queryTotal(sqlMap);
            List<ForumMuteRecordDto> list = null;
            if (total > 0) {
                list = forumMuteRecordService.queryList(sqlMap);
                // 这里只有一条禁言记录取第一个
                ForumMuteRecordDto forumMuteRecordDto = list.get(0);
                String recordText = "该用户已被管理员禁言，禁言时间为：" +
                        DateUtil.format(forumMuteRecordDto.getStartTime(), DatePattern.NORM_DATE_FORMATTER) + "~" +
                        DateUtil.format(forumMuteRecordDto.getEndTime(), DatePattern.NORM_DATE_FORMATTER);
                return Response.ok().wrap(recordText);
            }
        }
        return Response.ok();
    }

    /**
     * 详情
     *
     * @param id
     * @return
     */
    @GetMapping("forumMuteRecord/{id}")
    @RequirePermissions(values = "forumMute:info")
    @Operation(summary = "通过用户查询到禁言记录")
    public Response<List<ForumMuteRecordDto>> getRecordList(@PathVariable("id") Long id) {
        Map<String, Object> params = new HashMap<>();
        super.fillAuthorityData(params);

        params.put(LambdaUtil.getFieldName(ForumMuteRecordDto::getMobileUserId), id);
        List<ForumMuteRecordDto> result = forumMuteRecordService.queryList(params);
        if (CollectionUtils.isNotEmpty(result)) {
            for (ForumMuteRecordDto recordDto : result) {
                SysUserDto sysUserDto = sysUserService.selectCacheById(recordDto.getAuditUserId());
                if (sysUserDto != null) {
                    recordDto.setAuditUserName(sysUserDto.getUsername());
                }
            }
        }
        return Response.<List<ForumMuteRecordDto>>ok().wrap(result);
    }


    /**
     * 导出记录
     */
    @GetMapping("exportExcel")
    @RequirePermissions(values = "forumMute:exportExcel")
    @Operation(summary = "导出记录")
    public void exportExcel(HttpServletResponse hresp) {
        Request request = Request.configParamsNotPage(Request.parseParams(httpServletRequest));
        Map<String, Object> params = request.getParams();
        super.fillAuthorityData(params);

        List<ForumMuteDto> result = new ArrayList<>();
        int pageNo = 0;
        params.put("limit", 1000);
        while (true) {
            params.put("offset", pageNo++ * 1000);
            List<ForumMuteDto> list = forumMuteService.queryList(params);

            if (org.apache.commons.collections4.CollectionUtils.isEmpty(list)) {
                break;
            }
            result.addAll(list);
            if (list.size() < 1000) {
                break;
            }
        }

        // 填充数据
        for (ForumMuteDto forumMute : result) {
            MobileUserDto mobileUserDto = mobileUserService.selectCacheById(forumMute.getMobileUserId());
            if (mobileUserDto != null) {
                forumMute.setMobileUser(mobileUserDto);
            }
            request.put(LambdaUtil.getFieldName(ForumMuteRecordDto::getMobileUserId), forumMute.getMobileUserId());
            request.put(EXEC_TIME, DateUtils.format(new Date(), DateUtils.FormatType.SIMPLE));
            int queryTotal = forumMuteRecordService.queryTotal(request.getParams());
            if (queryTotal > 0) {
                forumMute.setStatus(SystemConstants.NO);
            } else {
                forumMute.setStatus(SystemConstants.YES);
            }
        }
        String[] headers = new String[]{"账号昵称", "账号手机号", "状态"};
        List<String[]> dataList = new ArrayList<>();
        for (ForumMuteDto data : result) {
            String[] item = new String[headers.length];
            item[0] = data.getMobileUser().getName();
            item[1] = data.getMobileUser().getMobile();
            if (data.getStatus().equals(SystemConstants.YES)) {
                item[2] = "正常";
            } else {
                item[2] = "禁言";
            }
            dataList.add(item);
        }
        POIUtils.exportExcel(hresp, "邻友圈禁言用户", headers, dataList, "禁言用户信息");

    }

    /**
     * 分页查询
     *
     * @param pageNo
     * @param pageSize
     * @return
     */
    @GetMapping("list")
    @RequirePermissions(values = "forumMute:list")
    @Operation(summary = "分页获取邻友圈禁言管理列表")
    public Response<Page<ForumMuteDto>> list(
            @Parameter(description = "从1开始的页码数") @RequestParam Integer pageNo,
            @Parameter(description = "每页多少条") @RequestParam Integer pageSize
    ) {
        //查询列表数据
        Request request = Request.configParams(Request.parseParams(httpServletRequest));

        super.fillAuthorityData(request.getParams());

        // 

        // 姓名
        if (StringUtils.isNotBlank(request.getString("name"))) {
            List<Long> ids = mobileUserBusiness.getIdList(request.getString("name"));
            if (CollectionUtils.isNotEmpty(ids)) {
                logger.debug("通过名称查询到的用户ids:{}", ids);
                request.put(SOURCEIDS, ids);
                request.getParams().remove("name");
            } else {
                request.put("name", SOURCEIDS);
            }
        }

        int total = forumMuteService.queryTotal(request.getParams());

        List<ForumMuteDto> list = null;
        if (total > 0) {
            list = forumMuteService.queryList(request.getParams());
            for (ForumMuteDto forumMute : list) {
                MobileUserDto mobileUserDto = mobileUserService.selectCacheById(forumMute.getMobileUserId());
                if (mobileUserDto != null) {
                    forumMute.setMobileUser(mobileUserDto);
                }
                request.put(LambdaUtil.getFieldName(ForumMuteRecordDto::getMobileUserId), forumMute.getMobileUserId());
                request.put(EXEC_TIME, DateUtils.format(new Date(), DateUtils.FormatType.SIMPLE));
                int queryTotal = forumMuteRecordService.queryTotal(request.getParams());
                if (queryTotal > 0) {
                    forumMute.setStatus(SystemConstants.NO);
                } else {
                    forumMute.setStatus(SystemConstants.YES);
                }
            }
        } else {
            list = new ArrayList<>();
        }

        Page<ForumMuteDto> page = new Page<>(request.getPageNo(), request.getPageSize(), total, list);
        return Response.<Page<ForumMuteDto>>ok().wrap(page);
    }

    /**
     * 编辑查询反显
     *
     * @param id
     * @return
     */
    @GetMapping("infoForEdit/{id}")
    @RequirePermissions(values = "forumMute:edit")
    @Operation(summary = "在编辑时根据id查询邻友圈禁言管理详情")
    public Response<ForumMuteDto> infoForEdit(@PathVariable("id") Long id) {

        Map<String, Object> params = new HashMap<>();
        super.fillAuthorityData(params);
        params.put(SystemConstants.ENTITY_ID_FLAG, String.valueOf(id));
        if (forumMuteService.queryTotal(params) <= 0) {
            return Response.error(SystemConstants.ILLEGAL_MSG);
        }

        ForumMuteDto forumMuteDto = forumMuteService.selectById(id);

        return Response.<ForumMuteDto>ok().wrap(forumMuteDto);
    }

    /**
     * 详情
     *
     * @param id
     * @return
     */
    @GetMapping("info/{id}")
    @RequirePermissions(values = "forumMute:info")
    @Operation(summary = "根据id查询邻友圈禁言管理的详情")
    public Response<ForumMuteDto> info(@PathVariable("id") Long id) {

        Map<String, Object> params = new HashMap<>();
        super.fillAuthorityData(params);
        params.put(SystemConstants.ENTITY_ID_FLAG, String.valueOf(id));
        if (forumMuteService.queryTotal(params) <= 0) {
            return Response.error(SystemConstants.ILLEGAL_MSG);
        }

        ForumMuteDto forumMuteDto = forumMuteService.selectById(id);

        return Response.<ForumMuteDto>ok().wrap(forumMuteDto);
    }

    /**
     * 保存
     *
     * @param forumMuteDto
     * @return
     */
    @PostMapping("save")
    @RequirePermissions(values = "forumMute:edit")
    @Operation(summary = "新增邻友圈禁言管理")
    public Response<Object> save(@RequestBody @Validated ForumMuteDto forumMuteDto) {

        //填充基础数据
        fillSaveCommonData(forumMuteDto);

        forumMuteService.save(forumMuteDto);

        return Response.ok();
    }


    /**
     * 修改
     *
     * @param forumMuteDto
     * @return
     */
    @PostMapping("update")
    @RequirePermissions(values = "forumMute:edit")
    @Operation(summary = "根据id修改邻友圈禁言管理")
    public Response<Object> update(@RequestBody @Validated ForumMuteDto forumMuteDto) {

        Map<String, Object> params = new HashMap<>();
        super.fillAuthorityData(params);
        params.put(SystemConstants.ENTITY_ID_FLAG, String.valueOf(forumMuteDto.getId()));
        if (forumMuteService.queryTotal(params) <= 0) {
            return Response.error(SystemConstants.ILLEGAL_MSG);
        }
        //填充基础数据
        fillEditCommonData(forumMuteDto);

        forumMuteService.updateById(forumMuteDto);

        return Response.ok();
    }

    /**
     * 批量删除
     *
     * @param ids
     * @return
     */
    @PostMapping("delete")
    @RequirePermissions(values = "forumMute:delete")
    @Operation(summary = "根据多条记录id批量删除邻友圈禁言管理")
    public Response<Object> delete(@RequestBody Long[] ids) {

        Map<String, Object> params = new HashMap<>();
        super.fillAuthorityData(params);

        for (Long id : ids) {

            params.remove(SystemConstants.ENTITY_ID_FLAG);
            params.put(SystemConstants.ENTITY_ID_FLAG, String.valueOf(id));

            if (forumMuteService.queryTotal(params) <= 0) {
                return Response.error(SystemConstants.ILLEGAL_MSG);
            }
        }

        forumMuteService.deleteBatch(ids);

        return Response.ok();
    }
}
